# -*- coding: utf-8 -*-

#    OriginDB
#    Copyright (C) 2010  Jason Power <power.jg@gmail.com>
#
#    This program is free software; you can redistribute it and/or modify
#    it under the terms of the GNU General Public License as published by
#    the Free Software Foundation; either version 2 of the License, or
#    (at your option) any later version.
#
#    This program is distributed in the hope that it will be useful,
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
#    GNU General Public License for more details.
#
#    You should have received a copy of the GNU General Public License along
#    with this program; if not, write to the Free Software Foundation, Inc.,
#    51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.

from PyQt4.QtGui import *
from PyQt4 import QtCore

from atom import Atom
from bond import Bond
from compound import Compound

import openbabel

class AddAtom(QUndoCommand):

	def __init__(self, atom, scene, pos, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("add atom")

		self.atom = atom
		self.scene = scene
		self.pos = pos

	def undo(self):
		oldAtom = openbabel.OBAtom()
		oldAtom.Duplicate(self.atom)
		self.pos = self.scene.compound.removeAtom(self.atom)
		self.atom = oldAtom

	def redo(self):
		self.atom = self.scene.compound.addAtom(self.atom, self.pos)

class RemoveAtom(QUndoCommand):

	def __init__(self, atom, scene, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("remove atom")

		self.atom = atom
		print self.atom.GetIdx(), self.atom.GetAtomicNum(), atom
		self.scene = scene

	def undo(self):
		print "undoing", self.atom.GetAtomicNum(), self.atom
		self.atom = self.scene.compound.addAtom(self.atom, self.pos)

	def redo(self):
		oldAtom = openbabel.OBAtom()
		oldAtom.Duplicate(self.atom)
		self.pos = self.scene.compound.removeAtom(self.atom)
		self.atom = oldAtom


class AddBond(QUndoCommand):

	def __init__(self, beginAtom, endAtom, typ, scene, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("add bond")

		self.beginAtom = beginAtom
		self.endAtom = endAtom
		self.typ = typ
		self.scene = scene

	def undo(self):
		self.beginAtom, self.endAtom, self.typ = self.scene.compound.removeBond(self.bond)

	def redo(self):
		self.bond = self.scene.compound.addBond(self.beginAtom, self.endAtom, self.typ)

class RemoveBond(QUndoCommand):

	def __init__(self, bond, scene, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("remove bond")

		self.bond = bond
		self.scene = scene

	def undo(self):
		self.bond = self.scene.compound.addBond(self.beginAtom, self.endAtom, self.typ)

	def redo(self):
		self.beginAtom, self.endAtom, self.typ = self.scene.compound.removeBond(self.bond)

class AddMolecule(QUndoCommand):

	def __init__(self, mol, scene, pos, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("add molecule")

		self.mol = mol
		self.scene = scene
		self.pos = pos
		#v = self.scene.compound.translateToAtomCoords(pos)
		#for atom in openbabel.OBMolAtomIter(self.mol):
			#va = atom.GetVector()
			#va += v
			#atom.SetVector(va)

	def undo(self):
		self.mol = self.scene.compound.removeMultiple(self.atoms, self.bonds)

	def redo(self):
		self.atoms, self.bonds = self.scene.compound.addMolecule(self.mol)

class ChangeAtomicNum(QUndoCommand):

	def __init__(self, atom, newNum, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("change atomic number")

		# atom is an Atom object NOT OBAtom
		self.atom = atom
		self.newNum = newNum

	def undo(self):
		self.newNum = self.atom.setAtomicNum(self.oldNum)

	def redo(self):
		self.oldNum = self.atom.setAtomicNum(self.newNum)

class ChangeBondType(QUndoCommand):

	def __init__(self, bond, newType, parent=None):
		QUndoCommand.__init__(self, parent)
		self.setText("change atomic number")

		# bond is an Bond object NOT OBBond
		self.bond = bond
		self.newType = newType

	def undo(self):
		self.newType = self.bond.setType(self.oldType)

	def redo(self):
		self.oldType = self.bond.setType(self.newType)
